package com.xyht.sca_s.student_manage_system.modules.examinePaymentInfrastructure.service.impl;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.deepoove.poi.XWPFTemplate;
import com.deepoove.poi.config.Configure;
import com.deepoove.poi.data.PictureRenderData;
import com.deepoove.poi.data.PictureType;
import com.deepoove.poi.data.Pictures;
import com.deepoove.poi.policy.PictureRenderPolicy;
import com.github.yulichang.wrapper.MPJLambdaWrapper;
import com.spire.doc.Document;
import com.spire.doc.FileFormat;
import com.xyht.sca_s.student_manage_system.common.commonReturn.CommonCodeEnum;
import com.xyht.sca_s.student_manage_system.common.commonReturn.CommonResult;
import com.xyht.sca_s.student_manage_system.common.commonReturn.ExceptionCast;
import com.xyht.sca_s.student_manage_system.common.commonReturn.ResponseResult;
import com.xyht.sca_s.student_manage_system.common.util.ApiModelUtil;
import com.xyht.sca_s.student_manage_system.common.util.CacheUtil;
import com.xyht.sca_s.student_manage_system.common.util.TimeUtil;
import com.xyht.sca_s.student_manage_system.modules.common.constant.FileSavePathConstant;
import com.xyht.sca_s.student_manage_system.modules.examinePaymentEquipment.entity.req.SmsPaymentExamineCancelReq;
import com.xyht.sca_s.student_manage_system.modules.examinePaymentEquipment.entity.req.SmsPaymentExamineEquipmentDetailTorsionReq;
import com.xyht.sca_s.student_manage_system.modules.examinePaymentEquipment.entity.req.SmsPaymentExamineEquipmentForcedReq;
import com.xyht.sca_s.student_manage_system.modules.examinePaymentEquipment.entity.resp.SmsPaymentExamineOriginSettingProcessResp;
import com.xyht.sca_s.student_manage_system.modules.examinePaymentInfrastructure.entity.SmsPaymentExamineInfrastructure;
import com.xyht.sca_s.student_manage_system.modules.examinePaymentInfrastructure.entity.SmsPaymentExamineInfrastructureDetail;
import com.xyht.sca_s.student_manage_system.modules.examinePaymentInfrastructure.entity.SmsPaymentExamineInfrastructureProcess;
import com.xyht.sca_s.student_manage_system.modules.examinePaymentInfrastructure.entity.req.SmsPaymentExamineInfrastructureAllowReq;
import com.xyht.sca_s.student_manage_system.modules.examinePaymentInfrastructure.entity.req.SmsPaymentExamineInfrastructureDetailReq;
import com.xyht.sca_s.student_manage_system.modules.examinePaymentInfrastructure.entity.req.SmsPaymentExamineInfrastructureHistoryReq;
import com.xyht.sca_s.student_manage_system.modules.examinePaymentInfrastructure.entity.req.SmsPaymentExamineInfrastructureReq;
import com.xyht.sca_s.student_manage_system.modules.examinePaymentInfrastructure.entity.resp.SmsPaymentExamineInfrastructureDetailResp;
import com.xyht.sca_s.student_manage_system.modules.examinePaymentInfrastructure.entity.resp.SmsPaymentExamineInfrastructureMpjResp;
import com.xyht.sca_s.student_manage_system.modules.examinePaymentInfrastructure.entity.resp.SmsPaymentExamineInfrastructureResp;
import com.xyht.sca_s.student_manage_system.modules.examinePaymentInfrastructure.entity.resp.SmsPaymentExamineInfrastructureUserResp;
import com.xyht.sca_s.student_manage_system.modules.examinePaymentInfrastructure.mapper.SmsPaymentExamineInfrastructureDetailMapper;
import com.xyht.sca_s.student_manage_system.modules.examinePaymentInfrastructure.mapper.SmsPaymentExamineInfrastructureMapper;
import com.xyht.sca_s.student_manage_system.modules.examinePaymentInfrastructure.mapper.SmsPaymentExamineInfrastructureMpjMapper;
import com.xyht.sca_s.student_manage_system.modules.examinePaymentInfrastructure.mapper.SmsPaymentExamineInfrastructureProcessMapper;
import com.xyht.sca_s.student_manage_system.modules.examinePaymentInfrastructure.service.SmsPaymentExamineInfrastructureService;
import com.xyht.sca_s.student_manage_system.modules.newTips.myEnum.AppTypeEnum;
import com.xyht.sca_s.student_manage_system.modules.newTips.myEnum.RangeTypeEnum;
import com.xyht.sca_s.student_manage_system.modules.newTips.myEnum.TipsTypeEnum;
import com.xyht.sca_s.student_manage_system.modules.newTips.util.NewTipsUtil;
import com.xyht.sca_s.student_manage_system.modules.user.entity.SmsRole;
import com.xyht.sca_s.student_manage_system.modules.user.entity.SmsUser;
import com.xyht.sca_s.student_manage_system.modules.user.mapper.SmsRoleMapper;
import com.xyht.sca_s.student_manage_system.modules.user.mapper.SmsUserMapper;
import org.apache.poi.hssf.usermodel.*;
import org.apache.poi.ss.usermodel.FillPatternType;
import org.apache.poi.ss.usermodel.IndexedColors;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.core.io.ClassPathResource;
import org.springframework.scheduling.annotation.Async;
import org.springframework.scheduling.annotation.AsyncResult;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletResponse;
import java.io.*;
import java.net.URLEncoder;
import java.util.*;
import java.util.concurrent.Future;
import java.util.stream.Collectors;

import static com.xyht.sca_s.student_manage_system.common.util.ParamCheckUtil.isNullOrEmpty;
import static com.xyht.sca_s.student_manage_system.modules.agreement.constant.agreementObjectTypeConstant.AGREEMENT_OBJECT_TYPE_PERSON;
import static com.xyht.sca_s.student_manage_system.modules.examinePaymentEquipment.constant.examineObjectTypeConstant.EXAMINE_OBJECT_TYPE_PERSON;
import static com.xyht.sca_s.student_manage_system.modules.examinePaymentEquipment.constant.examineObjectTypeConstant.EXAMINE_OBJECT_TYPE_ROLE;
import static com.xyht.sca_s.student_manage_system.modules.examinePaymentEquipment.constant.isExportProcessConstant.EXPORT_PROCESS_TRUE;
import static com.xyht.sca_s.student_manage_system.modules.examinePaymentEquipment.constant.paymentExamineStatusConstant.*;
import static com.xyht.sca_s.student_manage_system.modules.examinePaymentEquipment.constant.paymentExamineTypeConstant.*;
import static com.xyht.sca_s.student_manage_system.modules.student.constant.StudentInfoCommonConstant.PER_SHEET_NUM;

/**
 * <p>
 * 付款审批表（基础建设） 服务实现类
 * </p>
 *
 * @author XYHT
 * @since 2023-07-16
 */
@Service
public class SmsPaymentExamineInfrastructureServiceImpl extends ServiceImpl<SmsPaymentExamineInfrastructureMapper, SmsPaymentExamineInfrastructure> implements SmsPaymentExamineInfrastructureService {
    @Resource
    private FileSavePathConstant fileSavePathConstant;
    @Autowired
    private SmsPaymentExamineInfrastructureMapper smsPaymentExamineInfrastructureMapper;

    @Autowired
    private SmsPaymentExamineInfrastructureProcessMapper smsPaymentExamineInfrastructureProcessMapper;

    @Autowired
    private SmsPaymentExamineInfrastructureDetailMapper smsPaymentExamineInfrastructureDetailMapper;

    @Autowired
    private NewTipsUtil newTipsUtil;

    @Autowired
    private CacheUtil cacheUtil;

    @Autowired
    private SmsRoleMapper smsRoleMapper;

    @Autowired
    private SmsPaymentExamineInfrastructureMpjMapper smsPaymentExamineInfrastructureMpjMapper;

    @Override
    @Transactional
    public ResponseResult addPaymentExamine(SmsPaymentExamineInfrastructureReq req, String user_id) {
        List<SmsPaymentExamineInfrastructureProcess> fillProcessList =
                smsPaymentExamineInfrastructureProcessMapper.selectList(new QueryWrapper<SmsPaymentExamineInfrastructureProcess>()
                        .lambda()
                        .eq(SmsPaymentExamineInfrastructureProcess::getProcessIsApplicantEdit, true)
                        .eq(SmsPaymentExamineInfrastructureProcess::getProcessIsUse, true)
                        .orderByAsc(SmsPaymentExamineInfrastructureProcess::getProcessSort));
        if (fillProcessList != null && fillProcessList.size() > 0) {
            if (req.getProcessList() == null || req.getProcessList().size() < 1) {
                return CommonResult.failed(CommonCodeEnum.PAYMENT_ALLOW_USER_NOT_SETTING);
            }
            //判断申请人是否将全部需要编辑流程填写
            List<SmsPaymentExamineInfrastructureProcess> filterList = fillProcessList
                    .stream()
                    .filter(process -> {
                                List<String> result = req.getProcessList()
                                        .stream()
                                        .filter(fillProcess -> fillProcess.getProcessId().equals(process.getId()))
                                        .map(SmsPaymentExamineInfrastructureDetailReq::getId)
                                        .collect(Collectors.toList());
                                //匹配的去除  未匹配的留下
                                if (result.size() > 0) {
                                    return false;
                                } else {
                                    return true;
                                }
                            }
                    )
                    .collect(Collectors.toList());
            if (filterList.size() > 0) {
                return CommonResult.failed(CommonCodeEnum.PAYMENT_ALLOW_PROCESS_NOT_FILL);
            }
        }

        //创建申请表
        SmsPaymentExamineInfrastructure addPaymentExamine = new SmsPaymentExamineInfrastructure();
        BeanUtils.copyProperties(req, addPaymentExamine);
        addPaymentExamine.setPaymentApplyUserId(user_id);
        addPaymentExamine.setAllowStatus(EXAMINE_STATUS_WAIT_ALLOW);
        smsPaymentExamineInfrastructureMapper.insert(addPaymentExamine);

        if (addPaymentExamine.getId() == null) {
            ExceptionCast.cast(CommonResult.failed(CommonCodeEnum.FAIL));
        }
        String examine_id = addPaymentExamine.getId();

        //创建审批流程
        List<SmsPaymentExamineInfrastructureProcess> originProcessList =
                smsPaymentExamineInfrastructureProcessMapper.selectList(new QueryWrapper<SmsPaymentExamineInfrastructureProcess>()
                        .lambda()
                        .eq(SmsPaymentExamineInfrastructureProcess::getProcessIsUse, true)
                        .orderByAsc(SmsPaymentExamineInfrastructureProcess::getProcessSort));
        if (originProcessList == null || originProcessList.size() < 1) {
            ExceptionCast.cast(CommonResult.failed(CommonCodeEnum.PAYMENT_PROCESS_NOT_SETTING));
        }
        int sort = 1;
        for (SmsPaymentExamineInfrastructureProcess process : originProcessList) {
            //判断管理员是否配置初始流程
            if (!process.getProcessIsApplicantEdit()) {
                if (isNullOrEmpty(process.getProcessObjectId()) || isNullOrEmpty(process.getProcessObjectType())) {
                    ExceptionCast.cast(CommonResult.failed(CommonCodeEnum.PAYMENT_PROCESS_NOT_SETTING));
                }
            }

            SmsPaymentExamineInfrastructureDetail addDetail =
                    new SmsPaymentExamineInfrastructureDetail();

            addDetail.setExamineId(examine_id);
            addDetail.setProcessId(process.getId());
            addDetail.setProcessIsSign(process.getProcessIsSign());
            addDetail.setProcessIsStamp(process.getProcessIsStamp());
            addDetail.setProcessName(process.getProcessName());
            addDetail.setDetailAllowStatus(EXAMINE_STATUS_WAIT_ALLOW);

            addDetail.setDetailSort(sort++);

            //申请人可编辑流程
            if (process.getProcessIsApplicantEdit()) {
                List<SmsPaymentExamineInfrastructureDetailReq> filterList = req.getProcessList()
                        .stream()
                        .filter(fillProcess -> fillProcess.getProcessId().equals(process.getId()))
                        .collect(Collectors.toList());
                if (filterList.size() < 1) {
                    ExceptionCast.cast(CommonResult.failed(CommonCodeEnum.PAYMENT_ALLOW_PROCESS_NOT_FILL));
                }
                SmsPaymentExamineInfrastructureDetailReq fillProcessReq = filterList.get(0);

                if (isNullOrEmpty(fillProcessReq.getProcessObjectId())) {
                    ExceptionCast.cast(CommonResult.failed(CommonCodeEnum.INVALID_PARAM));
                }
                addDetail.setProcessObjectId(fillProcessReq.getProcessObjectId());
                addDetail.setProcessObjectType(EXAMINE_OBJECT_TYPE_PERSON); //可编辑默认为个人类型
            } else {
                addDetail.setProcessObjectId(process.getProcessObjectId());
                addDetail.setProcessObjectType(process.getProcessObjectType());
            }
            smsPaymentExamineInfrastructureDetailMapper.insert(addDetail);
        }

        //消息通知
        //通知流程第一个节点
        SmsPaymentExamineInfrastructureDetail firstDetail =
                smsPaymentExamineInfrastructureDetailMapper.selectOne(new QueryWrapper<SmsPaymentExamineInfrastructureDetail>()
                        .lambda()
                        .eq(SmsPaymentExamineInfrastructureDetail::getExamineId, examine_id)
                        .eq(SmsPaymentExamineInfrastructureDetail::getDetailSort, 1)
                        .orderByAsc(SmsPaymentExamineInfrastructureDetail::getDetailSort));
        RangeTypeEnum rangeTypeEnum;
        if (firstDetail.getProcessObjectType() == EXAMINE_OBJECT_TYPE_PERSON) {
            rangeTypeEnum = RangeTypeEnum.RANGE_TYPE_ENUM_PERSON;
        } else {
            rangeTypeEnum = RangeTypeEnum.RANGE_TYPE_ENUM_ROLE;
        }
        List<String> rangeList = new ArrayList<>();
        rangeList.add(firstDetail.getProcessObjectId());

        newTipsUtil.addNewTips(TipsTypeEnum.TIPS_TYPE_ENUM_ALLOW,
                user_id,
                rangeTypeEnum,
                rangeList,
                AppTypeEnum.APP_TYPE_ENUM_PAYMENT_EXAMINE_INFRASTRUCTURE,
                examine_id,
                firstDetail.getId());
        return CommonResult.success();
    }


    @Override
    @Transactional
    public ResponseResult cancelPaymentExamine(SmsPaymentExamineCancelReq smsPaymentExamineCancelReq, String user_id) {
        if (isNullOrEmpty(smsPaymentExamineCancelReq.getExamine_id())) {
            return CommonResult.failed(CommonCodeEnum.INVALID_PARAM);
        }

        //查看审批表是否存在且是否为本人
        SmsPaymentExamineInfrastructure paymentExamine =
                smsPaymentExamineInfrastructureMapper.selectOne(new QueryWrapper<SmsPaymentExamineInfrastructure>()
                        .lambda()
                        .eq(SmsPaymentExamineInfrastructure::getId, smsPaymentExamineCancelReq.getExamine_id())
                        .eq(SmsPaymentExamineInfrastructure::getPaymentApplyUserId, user_id));
        if (paymentExamine == null || isNullOrEmpty(paymentExamine.getId())) {
            return CommonResult.failed(CommonCodeEnum.PAYMENT_NOT_EXIST);
        }
        if (paymentExamine.getAllowStatus() != EXAMINE_STATUS_WAIT_ALLOW) {
            return CommonResult.failed(CommonCodeEnum.PAYMENT_CANCEL_FAIL_ALLOWED);
        }

        //判断是否审批中
//        List<SmsPaymentExamineInfrastructureDetail> detailList =
//                smsPaymentExamineInfrastructureDetailMapper.selectList(new QueryWrapper<SmsPaymentExamineInfrastructureDetail>()
//                        .lambda()
//                        .eq(SmsPaymentExamineInfrastructureDetail::getExamineId, smsPaymentExamineCancelReq.getExamine_id())
//                        .eq(SmsPaymentExamineInfrastructureDetail::getDetailAllowStatus, EXAMINE_STATUS_PASS));
//        if (detailList != null && detailList.size() > 0) {
//            return CommonResult.failed(CommonCodeEnum.PAYMENT_CANCEL_FAIL_ALLOWING);
//        }

        //撤回审批
        SmsPaymentExamineInfrastructure cancelExamine = new SmsPaymentExamineInfrastructure();
        cancelExamine.setId(smsPaymentExamineCancelReq.getExamine_id());
        cancelExamine.setAllowStatus(EXAMINE_STATUS_CANCEL);
        cancelExamine.setEndTime(new Date());
        smsPaymentExamineInfrastructureMapper.updateById(cancelExamine);

        //修改节点状态
        SmsPaymentExamineInfrastructureDetail cancelExamineDetail = new SmsPaymentExamineInfrastructureDetail();
        cancelExamineDetail.setDetailAllowStatus(EXAMINE_STATUS_CANCEL);

        smsPaymentExamineInfrastructureDetailMapper.update(cancelExamineDetail, new QueryWrapper<SmsPaymentExamineInfrastructureDetail>()
                .lambda()
                .eq(SmsPaymentExamineInfrastructureDetail::getExamineId, smsPaymentExamineCancelReq.getExamine_id())
                .eq(SmsPaymentExamineInfrastructureDetail::getDetailAllowStatus,EXAMINE_STATUS_WAIT_ALLOW));

        //消息通知
        newTipsUtil.cancelFinishTips(smsPaymentExamineCancelReq.getExamine_id());

        return CommonResult.success();
    }

    @Override
    public ResponseResult getPaymentExamineList(String user_id, Integer examine_type,String search_str, Integer pageNum, Integer pageSize) {
        if (isNullOrEmpty(examine_type)) {
            return CommonResult.failed(CommonCodeEnum.INVALID_PARAM);
        }
        List<SmsPaymentExamineInfrastructureResp> respList = new ArrayList<>();
        int total = 0;
        if (examine_type == EXAMINE_TYPE_APPLY) {
            Page<SmsPaymentExamineInfrastructure> page = new Page<>(pageNum, pageSize);
            QueryWrapper<SmsPaymentExamineInfrastructure> queryWrapper = new QueryWrapper<>();
            queryWrapper.lambda()
                    .eq(SmsPaymentExamineInfrastructure::getPaymentApplyUserId, user_id)
                    .orderByDesc(SmsPaymentExamineInfrastructure::getCreateTime);
            if (!isNullOrEmpty(search_str)) {
                List<String> userIdList = smsUserMapper.selectList(new QueryWrapper<SmsUser>()
                                .lambda()
                                .like(SmsUser::getRealName, search_str))
                        .stream()
                        .map(SmsUser::getId)
                        .collect(Collectors.toList());
                queryWrapper.lambda().and(wrapper -> {
                    wrapper.like(SmsPaymentExamineInfrastructure::getPaymentContractName, search_str)
                            .or()
                            .like(SmsPaymentExamineInfrastructure::getPaymentContractNum, search_str)
                            .or()
                            .like(SmsPaymentExamineInfrastructure::getPaymentApplyMoney, search_str);
                    if (userIdList.size() > 0) {
                        wrapper.or()
                                .in(SmsPaymentExamineInfrastructure::getPaymentApplyUserId, userIdList);
                    }
                });
            }
            smsPaymentExamineInfrastructureMapper.selectPage(page, queryWrapper);
            respList = page.getRecords()
                    .stream()
                    .map(smsExamine -> {
                        SmsPaymentExamineInfrastructureResp smsPaymentExamineResp =
                                new SmsPaymentExamineInfrastructureResp();
                        BeanUtils.copyProperties(smsExamine, smsPaymentExamineResp);
                        smsPaymentExamineResp.setExamineId(smsExamine.getId());

                        SmsUser smsUser = cacheUtil.getUserInfo(smsExamine.getPaymentApplyUserId());
                        SmsPaymentExamineInfrastructureUserResp smsExamineUserResp = new SmsPaymentExamineInfrastructureUserResp();
                        if (smsUser != null) {
                            BeanUtils.copyProperties(smsUser, smsExamineUserResp);
                        }
                        smsPaymentExamineResp.setApplyUserInfo(smsExamineUserResp);

                        return smsPaymentExamineResp;
                    })
                    .collect(Collectors.toList());
            total = (int) page.getTotal();
        } else if (examine_type == EXAMINE_TYPE_ALLOWED) {
            Page<SmsPaymentExamineInfrastructureMpjResp> page = new Page<>(pageNum, pageSize);
            MPJLambdaWrapper<SmsPaymentExamineInfrastructureDetail> mpjLambdaWrapper = new MPJLambdaWrapper<>();
            mpjLambdaWrapper.selectAll(SmsPaymentExamineInfrastructureDetail.class)
                    .selectAll(SmsPaymentExamineInfrastructure.class)
                    .selectAs(SmsPaymentExamineInfrastructure::getCreateTime, "examineCreateTime")
                    .selectAs(SmsPaymentExamineInfrastructureDetail::getId, "detailId")
                    .leftJoin(SmsPaymentExamineInfrastructure.class, SmsPaymentExamineInfrastructure::getId, SmsPaymentExamineInfrastructureDetail::getExamineId)
                    .eq(SmsPaymentExamineInfrastructureDetail::getDetailAllowUserId, user_id)
//                    .orderByDesc(SmsPaymentExamineInfrastructure::getCreateTime)
                    .orderByDesc(SmsPaymentExamineInfrastructureDetail::getDetailAllowTime)
            ;

            mpjLambdaWrapper.and(wrapper -> {
                wrapper.eq(SmsPaymentExamineInfrastructureDetail::getDetailAllowStatus, EXAMINE_STATUS_PASS)
                        .or()
                        .eq(SmsPaymentExamineInfrastructureDetail::getDetailAllowStatus, EXAMINE_STATUS_DENY);
            });
            if (!isNullOrEmpty(search_str)) {
                List<String> userIdList = smsUserMapper.selectList(new QueryWrapper<SmsUser>()
                                .lambda()
                                .like(SmsUser::getRealName, search_str))
                        .stream()
                        .map(SmsUser::getId)
                        .collect(Collectors.toList());
                mpjLambdaWrapper.and(wrapper -> {
                    wrapper.like(SmsPaymentExamineInfrastructure::getPaymentContractName, search_str)
                            .or()
                            .like(SmsPaymentExamineInfrastructure::getPaymentContractNum, search_str)
                            .or()
                            .like(SmsPaymentExamineInfrastructure::getPaymentApplyMoney, search_str);
                    if (userIdList.size() > 0) {
                        wrapper.or()
                                .in(SmsPaymentExamineInfrastructure::getPaymentApplyUserId, userIdList);
                    }
                });
            }

            smsPaymentExamineInfrastructureMpjMapper.selectJoinPage(page, SmsPaymentExamineInfrastructureMpjResp.class, mpjLambdaWrapper);

            respList = page.getRecords()
                    .stream()
                    .map(smsExamineMPJResp -> {
                        SmsPaymentExamineInfrastructureResp smsExamineResp = new SmsPaymentExamineInfrastructureResp();
                        BeanUtils.copyProperties(smsExamineMPJResp, smsExamineResp);
                        smsExamineResp.setCreateTime(smsExamineMPJResp.getExamineCreateTime());

                        SmsUser applyUser = cacheUtil.getUserInfo(smsExamineResp.getPaymentApplyUserId());
                        SmsPaymentExamineInfrastructureUserResp smsExamineUserResp = new SmsPaymentExamineInfrastructureUserResp();
                        if (applyUser != null) {
                            BeanUtils.copyProperties(applyUser, smsExamineUserResp);
                        }
                        smsExamineResp.setApplyUserInfo(smsExamineUserResp);

                        SmsUser allowUser = cacheUtil.getUserInfo(smsExamineResp.getDetailAllowUserId());
                        SmsPaymentExamineInfrastructureUserResp smsExamineAllowUserResp = new SmsPaymentExamineInfrastructureUserResp();
                        if (allowUser != null) {
                            BeanUtils.copyProperties(allowUser, smsExamineAllowUserResp);
                        }
                        smsExamineResp.setAllowUserInfo(smsExamineAllowUserResp);

                        return smsExamineResp;
                    })
                    .collect(Collectors.toList());
            total = (int) page.getTotal();
        } else if (examine_type == EXAMINE_TYPE_ALLOW_WAIT_ME) {
            List<String> roleList = cacheUtil.getRoleList(user_id);

            //获取所有待审批申请流程节点
            List<SmsPaymentExamineInfrastructureDetail> allDetailList =
                    smsPaymentExamineInfrastructureDetailMapper.selectList(new QueryWrapper<SmsPaymentExamineInfrastructureDetail>()
                            .lambda()
                            .eq(SmsPaymentExamineInfrastructureDetail::getDetailAllowStatus, EXAMINE_STATUS_WAIT_ALLOW));

            List<SmsPaymentExamineInfrastructureDetail> filterDetailList = allDetailList.stream()
                    .filter(detail -> {
                        if (detail.getProcessObjectType() == EXAMINE_OBJECT_TYPE_PERSON) {
                            if (!detail.getProcessObjectId().equals(user_id)) {
                                return false;
                            }
                        } else {
                            List<String> filterRoleList = roleList.stream().filter(role -> role.equals(detail.getProcessObjectId())).collect(Collectors.toList());
                            if (filterRoleList.size() < 1) {
                                return false;
                            }
                        }

                        if (detail.getDetailSort().equals(1)) {
                            return true;
                        }
                        //判断上一个流程节点是否完成
                        SmsPaymentExamineInfrastructureDetail preDetail =
                                smsPaymentExamineInfrastructureDetailMapper.selectOne(new QueryWrapper<SmsPaymentExamineInfrastructureDetail>()
                                        .lambda()
                                        .eq(SmsPaymentExamineInfrastructureDetail::getExamineId, detail.getExamineId())
                                        .eq(SmsPaymentExamineInfrastructureDetail::getDetailSort, detail.getDetailSort() - 1)
                                        .eq(SmsPaymentExamineInfrastructureDetail::getDetailAllowStatus, EXAMINE_STATUS_PASS));
                        if (preDetail == null || isNullOrEmpty(preDetail.getId())) {
                            return false;
                        }
                        return true;
                    })
                    .collect(Collectors.toList());
            if (filterDetailList.size() > 0) {
                List<String> detailIDList = filterDetailList.stream().map(SmsPaymentExamineInfrastructureDetail::getId).collect(Collectors.toList());

                Page<SmsPaymentExamineInfrastructureMpjResp> page = new Page<>(pageNum, pageSize);
                MPJLambdaWrapper<SmsPaymentExamineInfrastructureDetail> mpjLambdaWrapper = new MPJLambdaWrapper<>();
                mpjLambdaWrapper.selectAll(SmsPaymentExamineInfrastructureDetail.class)
                        .selectAll(SmsPaymentExamineInfrastructure.class)
                        .selectAs(SmsPaymentExamineInfrastructure::getCreateTime, "examineCreateTime")
                        .selectAs(SmsPaymentExamineInfrastructureDetail::getId, "detailId")
                        .leftJoin(SmsPaymentExamineInfrastructure.class, SmsPaymentExamineInfrastructure::getId, SmsPaymentExamineInfrastructureDetail::getExamineId)
                        .in(SmsPaymentExamineInfrastructureDetail::getId, detailIDList)
                        .orderByDesc(SmsPaymentExamineInfrastructure::getCreateTime)
                        .orderByDesc(SmsPaymentExamineInfrastructureDetail::getCreateTime)
                ;

                if (!isNullOrEmpty(search_str)) {
                    List<String> userIdList = smsUserMapper.selectList(new QueryWrapper<SmsUser>()
                                    .lambda()
                                    .like(SmsUser::getRealName, search_str))
                            .stream()
                            .map(SmsUser::getId)
                            .collect(Collectors.toList());
                    mpjLambdaWrapper.and(wrapper -> {
                        wrapper.like(SmsPaymentExamineInfrastructure::getPaymentContractName, search_str)
                                .or()
                                .like(SmsPaymentExamineInfrastructure::getPaymentContractNum, search_str)
                                .or()
                                .like(SmsPaymentExamineInfrastructure::getPaymentApplyMoney, search_str);
                        if (userIdList.size() > 0) {
                            wrapper.or()
                                    .in(SmsPaymentExamineInfrastructure::getPaymentApplyUserId, userIdList);
                        }
                    });
                }

                smsPaymentExamineInfrastructureMpjMapper.selectJoinPage(page, SmsPaymentExamineInfrastructureMpjResp.class, mpjLambdaWrapper);

                respList = page.getRecords()
                        .stream()
                        .map(smsExamineMPJResp -> {
                            SmsPaymentExamineInfrastructureResp smsExamineResp = new SmsPaymentExamineInfrastructureResp();
                            BeanUtils.copyProperties(smsExamineMPJResp, smsExamineResp);
                            smsExamineResp.setCreateTime(smsExamineMPJResp.getExamineCreateTime());

                            SmsUser applyUser = cacheUtil.getUserInfo(smsExamineResp.getPaymentApplyUserId());
                            SmsPaymentExamineInfrastructureUserResp smsExamineUserResp = new SmsPaymentExamineInfrastructureUserResp();
                            if (applyUser != null) {
                                BeanUtils.copyProperties(applyUser, smsExamineUserResp);
                            }
                            smsExamineResp.setApplyUserInfo(smsExamineUserResp);

                            return smsExamineResp;
                        })
                        .collect(Collectors.toList());
                total = (int) page.getTotal();
            }
        }
        return CommonResult.success(respList, total);
    }

    @Override
    public ResponseResult getPaymentExamineDetail(String examine_id, String user_id) {
        if (isNullOrEmpty(examine_id)) {
            return CommonResult.failed(CommonCodeEnum.INVALID_PARAM);
        }
        SmsPaymentExamineInfrastructure paymentExamine = smsPaymentExamineInfrastructureMapper.selectById(examine_id);
        if (paymentExamine == null || isNullOrEmpty(paymentExamine.getId())) {
            return CommonResult.failed(CommonCodeEnum.PAYMENT_NOT_EXIST);
        }

        SmsPaymentExamineInfrastructureResp paymentExamineResp = new SmsPaymentExamineInfrastructureResp();
        BeanUtils.copyProperties(paymentExamine, paymentExamineResp);
        paymentExamineResp.setExamineId(paymentExamine.getId());

        SmsUser smsUser = cacheUtil.getUserInfo(paymentExamineResp.getPaymentApplyUserId());
        SmsPaymentExamineInfrastructureUserResp smsExamineUserResp = new SmsPaymentExamineInfrastructureUserResp();
        if (smsUser != null) {
            BeanUtils.copyProperties(smsUser, smsExamineUserResp);
        }
        paymentExamineResp.setApplyUserInfo(smsExamineUserResp);

        List<SmsPaymentExamineInfrastructureDetailResp> detailRespList =
                smsPaymentExamineInfrastructureDetailMapper.selectList(new QueryWrapper<SmsPaymentExamineInfrastructureDetail>()
                        .lambda()
                        .eq(SmsPaymentExamineInfrastructureDetail::getExamineId, examine_id)
                        .orderByAsc(SmsPaymentExamineInfrastructureDetail::getDetailSort))
                        .stream()
                        .map(detail -> {
                            SmsPaymentExamineInfrastructureDetailResp detailResp = new SmsPaymentExamineInfrastructureDetailResp();
                            BeanUtils.copyProperties(detail, detailResp);

                            if (!isNullOrEmpty(detailResp.getDetailAllowUserId())) {
                                SmsUser userInfo = cacheUtil.getUserInfo(detailResp.getDetailAllowUserId());
                                SmsPaymentExamineInfrastructureUserResp paymentExamineUserResp = new SmsPaymentExamineInfrastructureUserResp();
                                if (userInfo != null) {
                                    BeanUtils.copyProperties(userInfo, paymentExamineUserResp);
                                }
                                detailResp.setAllowUserInfo(paymentExamineUserResp);
                            }

                            if (detail.getProcessObjectType() == EXAMINE_OBJECT_TYPE_PERSON) {
                                SmsUser user = cacheUtil.getUserInfo(detail.getProcessObjectId());
                                if (user != null) {
                                    detailResp.setObjectName(user.getRealName());
                                    detailResp.setObjectPic(user.getUserPic());
                                }
                            } else {
                                SmsRole role = smsRoleMapper.selectById(detail.getProcessObjectId());
                                if (role != null) {
                                    detailResp.setObjectName(role.getRoleName());
                                }
                            }
                            return detailResp;
                        })
                        .collect(Collectors.toList());
        paymentExamineResp.setDetailList(detailRespList);
        return CommonResult.success(paymentExamineResp);
    }

    @Override
    @Transactional
    public ResponseResult allowPaymentExamine(SmsPaymentExamineInfrastructureAllowReq smsPaymentExamineAllowReq, String user_id) {
        if (isNullOrEmpty(smsPaymentExamineAllowReq.getExamine_id()) || isNullOrEmpty(smsPaymentExamineAllowReq.getDetail_id())
                || isNullOrEmpty(smsPaymentExamineAllowReq.getDetailAllowStatus())) {
            return CommonResult.failed(CommonCodeEnum.INVALID_PARAM);
        }

        if (smsPaymentExamineAllowReq.getDetailAllowStatus() != EXAMINE_STATUS_PASS
                && smsPaymentExamineAllowReq.getDetailAllowStatus() != EXAMINE_STATUS_DENY) {
            return CommonResult.failed(CommonCodeEnum.INVALID_PARAM);
        }

        SmsPaymentExamineInfrastructureDetail paymentExamineDetail =
                smsPaymentExamineInfrastructureDetailMapper.selectOne(new QueryWrapper<SmsPaymentExamineInfrastructureDetail>()
                        .lambda()
                        .eq(SmsPaymentExamineInfrastructureDetail::getExamineId, smsPaymentExamineAllowReq.getExamine_id())
                        .eq(SmsPaymentExamineInfrastructureDetail::getId, smsPaymentExamineAllowReq.getDetail_id())
                        .eq(SmsPaymentExamineInfrastructureDetail::getDetailAllowStatus, EXAMINE_STATUS_WAIT_ALLOW));
        if (paymentExamineDetail == null || isNullOrEmpty(paymentExamineDetail.getId())) {
            return CommonResult.failed(CommonCodeEnum.PAYMENT_ALLOW_FAIL);
        }

        //判断该节点是否本人审批（防止跳节点审批）
        if (paymentExamineDetail.getProcessObjectType() == EXAMINE_OBJECT_TYPE_PERSON) {
            if (!paymentExamineDetail.getProcessObjectId().equals(user_id)) {
                return CommonResult.failed(CommonCodeEnum.PAYMENT_ALLOW_FAIL);
            }
        } else {
            List<String> roleList = cacheUtil.getRoleList(user_id);
            List<String> filterRoleList = roleList.stream().filter(role -> role.equals(paymentExamineDetail.getProcessObjectId())).collect(Collectors.toList());
            if (filterRoleList.size() < 1) {
                return CommonResult.failed(CommonCodeEnum.PAYMENT_ALLOW_FAIL);
            }
        }

        if (!paymentExamineDetail.getDetailSort().equals(1)) {
            SmsPaymentExamineInfrastructureDetail preDetail =
                    smsPaymentExamineInfrastructureDetailMapper.selectOne(new QueryWrapper<SmsPaymentExamineInfrastructureDetail>()
                            .lambda()
                            .eq(SmsPaymentExamineInfrastructureDetail::getExamineId, smsPaymentExamineAllowReq.getExamine_id())
                            .eq(SmsPaymentExamineInfrastructureDetail::getDetailSort, paymentExamineDetail.getDetailSort() - 1));
            if (preDetail != null && !isNullOrEmpty(preDetail.getId())) {
                if (preDetail.getDetailAllowStatus() != EXAMINE_STATUS_PASS) {
                    return CommonResult.failed(CommonCodeEnum.PAYMENT_ALLOW_FAIL);
                }
            }
        }

        //判断是否监理部门
        if (paymentExamineDetail.getProcessName().equals("监理部门")) {
            if (isNullOrEmpty(smsPaymentExamineAllowReq.getJianliDepartmentName())) {
                return CommonResult.failed(CommonCodeEnum.PAYMENT_PROCESS_JIANLI_NOT_FILL);
            }

            SmsPaymentExamineInfrastructure updateExamine = new SmsPaymentExamineInfrastructure();
            updateExamine.setId(smsPaymentExamineAllowReq.getExamine_id());
            updateExamine.setJianliDepartmentName(smsPaymentExamineAllowReq.getJianliDepartmentName());

            smsPaymentExamineInfrastructureMapper.updateById(updateExamine);
        }

        //判断是否审计部门
        if (paymentExamineDetail.getProcessName().equals("审计部门")) {
            if (isNullOrEmpty(smsPaymentExamineAllowReq.getShenjiDepartmentName())) {
                return CommonResult.failed(CommonCodeEnum.PAYMENT_PROCESS_SHENJI_NOT_FILL);
            }

            SmsPaymentExamineInfrastructure updateExamine = new SmsPaymentExamineInfrastructure();
            updateExamine.setId(smsPaymentExamineAllowReq.getExamine_id());
            updateExamine.setShenjiDepartmentName(smsPaymentExamineAllowReq.getShenjiDepartmentName());

            smsPaymentExamineInfrastructureMapper.updateById(updateExamine);
        }


        //判断是否财务部 财务部填写审批金额
        if (smsPaymentExamineAllowReq.getDetailAllowStatus() == EXAMINE_STATUS_PASS && paymentExamineDetail.getProcessName().equals("财务部")) {
            if (isNullOrEmpty(smsPaymentExamineAllowReq.getPaymentExamineMoney())) {
                return CommonResult.failed(CommonCodeEnum.PAYMENT_PROCESS_FINANCE_NOT_FILL);
            }

            SmsPaymentExamineInfrastructure updateExamine = new SmsPaymentExamineInfrastructure();
            updateExamine.setId(smsPaymentExamineAllowReq.getExamine_id());
            updateExamine.setPaymentExamineMoney(smsPaymentExamineAllowReq.getPaymentExamineMoney());

            smsPaymentExamineInfrastructureMapper.updateById(updateExamine);
        }

        SmsPaymentExamineInfrastructureDetail allowDetail = new SmsPaymentExamineInfrastructureDetail();
        allowDetail.setId(smsPaymentExamineAllowReq.getDetail_id());
        allowDetail.setDetailAllowStatus(smsPaymentExamineAllowReq.getDetailAllowStatus());
        if (!isNullOrEmpty(smsPaymentExamineAllowReq.getDetailAllowOpinion())) {
            allowDetail.setDetailAllowOpinion(smsPaymentExamineAllowReq.getDetailAllowOpinion());
        }
        Date nowDate = new Date();
        allowDetail.setDetailAllowTime(nowDate);
        allowDetail.setDetailAllowUserId(user_id);

        if (paymentExamineDetail.getProcessIsSign()) {
            if (isNullOrEmpty(smsPaymentExamineAllowReq.getDetailAllowSign())) {
                return CommonResult.failed(CommonCodeEnum.INVALID_PARAM);
            }
            allowDetail.setDetailAllowSign(smsPaymentExamineAllowReq.getDetailAllowSign());
        }
        if (paymentExamineDetail.getProcessIsStamp()) {
            if (isNullOrEmpty(smsPaymentExamineAllowReq.getDetailAllowStamp())) {
                return CommonResult.failed(CommonCodeEnum.INVALID_PARAM);
            }
            allowDetail.setDetailAllowStamp(smsPaymentExamineAllowReq.getDetailAllowStamp());
        }
        smsPaymentExamineInfrastructureDetailMapper.updateById(allowDetail);

        boolean is_done = false;

        //判断是否最后一个节点 是否驳回
        Integer detailCount = smsPaymentExamineInfrastructureDetailMapper.selectCount(new QueryWrapper<SmsPaymentExamineInfrastructureDetail>()
                .lambda()
                .eq(SmsPaymentExamineInfrastructureDetail::getExamineId, smsPaymentExamineAllowReq.getExamine_id()));
        if (detailCount.equals(paymentExamineDetail.getDetailSort()) || smsPaymentExamineAllowReq.getDetailAllowStatus() == EXAMINE_STATUS_DENY) {
            is_done = true;

            SmsPaymentExamineInfrastructure updatePaymentExamine = new SmsPaymentExamineInfrastructure();
            updatePaymentExamine.setId(smsPaymentExamineAllowReq.getExamine_id());
            updatePaymentExamine.setEndTime(nowDate);
            updatePaymentExamine.setAllowStatus(smsPaymentExamineAllowReq.getDetailAllowStatus());
            smsPaymentExamineInfrastructureMapper.updateById(updatePaymentExamine);
        }

        //节点驳回 重置其余节点状态
        if (smsPaymentExamineAllowReq.getDetailAllowStatus() == EXAMINE_STATUS_DENY) {
            SmsPaymentExamineInfrastructureDetail updateDenyDetail =
                    new SmsPaymentExamineInfrastructureDetail();
            updateDenyDetail.setDetailAllowStatus(EXAMINE_STATUS_DENY_FINISH);
            smsPaymentExamineInfrastructureDetailMapper.update(updateDenyDetail, new QueryWrapper<SmsPaymentExamineInfrastructureDetail>()
                    .lambda()
                    .eq(SmsPaymentExamineInfrastructureDetail::getExamineId, smsPaymentExamineAllowReq.getExamine_id())
                    .eq(SmsPaymentExamineInfrastructureDetail::getDetailAllowStatus, EXAMINE_STATUS_WAIT_ALLOW));
        }

        //消息通知
        if (is_done) {
            boolean result_status = false;
            if (smsPaymentExamineAllowReq.getDetailAllowStatus() == EXAMINE_STATUS_PASS) {
                result_status = true;
            }
            newTipsUtil.allowFinishTips(smsPaymentExamineAllowReq.getExamine_id(), user_id, result_status);
        } else {
            SmsPaymentExamineInfrastructureDetail nextDetail =
                    smsPaymentExamineInfrastructureDetailMapper.selectOne(new QueryWrapper<SmsPaymentExamineInfrastructureDetail>()
                            .lambda()
                            .eq(SmsPaymentExamineInfrastructureDetail::getExamineId, smsPaymentExamineAllowReq.getExamine_id())
                            .eq(SmsPaymentExamineInfrastructureDetail::getDetailSort, paymentExamineDetail.getDetailSort() + 1));
            RangeTypeEnum rangeTypeEnum = RangeTypeEnum.RANGE_TYPE_ENUM_PERSON;
            if (nextDetail.getProcessObjectType() == EXAMINE_OBJECT_TYPE_ROLE) {
                rangeTypeEnum = RangeTypeEnum.RANGE_TYPE_ENUM_ROLE;
            }
            List<String> rangeIDList = new ArrayList<>();
            rangeIDList.add(nextDetail.getProcessObjectId());
            newTipsUtil.allowContinueTips(smsPaymentExamineAllowReq.getExamine_id(),
                    user_id,
                    rangeTypeEnum,
                    rangeIDList,
                    nextDetail.getId());
        }
        return CommonResult.success();
    }

    @Override
    public ResponseResult getPaymentExamineOriginSettingProcess() {
        List<SmsPaymentExamineOriginSettingProcessResp> respList =
                smsPaymentExamineInfrastructureProcessMapper.selectList(new QueryWrapper<SmsPaymentExamineInfrastructureProcess>()
                        .lambda()
                        .eq(SmsPaymentExamineInfrastructureProcess::getProcessIsApplicantEdit, true)
                        .eq(SmsPaymentExamineInfrastructureProcess::getProcessIsUse, true)
                        .orderByAsc(SmsPaymentExamineInfrastructureProcess::getProcessSort))
                        .stream()
                        .map(process -> {
                            SmsPaymentExamineOriginSettingProcessResp smsPaymentExamineOriginSettingProcessResp =
                                    new SmsPaymentExamineOriginSettingProcessResp();
                            BeanUtils.copyProperties(process, smsPaymentExamineOriginSettingProcessResp);
                            return smsPaymentExamineOriginSettingProcessResp;
                        })
                        .collect(Collectors.toList());
        return CommonResult.success(respList);
    }

    @Override
    public Future<ResponseResult> tableDownload(String apply_id, HttpServletResponse response) {
        SmsPaymentExamineInfrastructure paymentExamineEquipment = smsPaymentExamineInfrastructureMapper.selectById(apply_id);
        if (paymentExamineEquipment == null || paymentExamineEquipment.getId() == null) {
            return new AsyncResult<>(CommonResult.failed(CommonCodeEnum.PAYMENT_NOT_EXIST));
        }
//        if (paymentExamineEquipment.getAllowStatus() == WORK_STATUS_WAIT_ALLOW) {
//            return new AsyncResult<>(CommonResult.failed(CommonCodeEnum.WORK_APPLICATION_DOWNLOAD_FAIL));
//        }

        String OSName = System.getProperty("os.name");
        String filePath = OSName.toLowerCase().startsWith("win") ? fileSavePathConstant.getFILE_DOWNLOAD_PATH()
                : fileSavePathConstant.getFILE_DOWNLOAD_PATH_LINUX();

        String newFilePath = filePath + apply_id + ".docx";
        String pdfFilePath = filePath + apply_id + ".pdf";

        File pdfFile = new File(pdfFilePath);
//        if (!pdfFile.exists()) {
            try {

                String signTime = TimeUtil.DateHanZiSimpleFormat(paymentExamineEquipment.getPaymentContractSignTime());
                String createTime = TimeUtil.DateHanZiSimpleFormat(paymentExamineEquipment.getCreateTime());

                List<String> picTagList = new ArrayList<>();

                Map<String, Object> map = new HashMap<>();
                map.put("contractName", filterResultNull(paymentExamineEquipment.getPaymentContractName()));
                map.put("signTime", filterResultNull(signTime));
                map.put("createTime", filterResultNull(createTime));
                map.put("contractNum", filterResultNull(paymentExamineEquipment.getPaymentContractNum()));
                map.put("contractMoney", filterResultNull(String.valueOf(paymentExamineEquipment.getPaymentContractMoney())));
                map.put("paidMoney", filterResultNull(String.valueOf(paymentExamineEquipment.getPaymentPaidMoney())));
                map.put("applyMoney", filterResultNull(String.valueOf(paymentExamineEquipment.getPaymentApplyMoney())));
                map.put("invoice", filterResultNull(String.valueOf(paymentExamineEquipment.getPaymentInvoice())));
                map.put("examineMoney", filterResultNull(String.valueOf(paymentExamineEquipment.getPaymentExamineMoney())));
                map.put("totalInvoice", filterResultNull(String.valueOf(paymentExamineEquipment.getPaymentTotalInvoice().toString())));
                map.put("description", filterResultNull(paymentExamineEquipment.getPaymentDescription()));
                map.put("companyName", filterResultNull(paymentExamineEquipment.getPaymentCompanyName()));
                map.put("bankAccount", filterResultNull(paymentExamineEquipment.getPaymentBankAccount()));
                map.put("bank", filterResultNull(paymentExamineEquipment.getPaymentBank()));

                //监理 审计
                map.put("jianliDepartmentName", filterResultNull(String.valueOf(paymentExamineEquipment.getJianliDepartmentName())));
                map.put("shenjiDepartmentName", filterResultNull(String.valueOf(paymentExamineEquipment.getShenjiDepartmentName())));
                map.put("applyOpinion", filterResultNull(String.valueOf(paymentExamineEquipment.getApplyOpinion())));

                //经办人签名（申请人）
                String[] splitStr1 = paymentExamineEquipment.getSign().split("=");
                String fileName1 = splitStr1[splitStr1.length - 1];

                File file1 = new File(filePath + fileName1);
                if (file1.exists()) {
                    InputStream inputStream = new FileInputStream(file1);
                    PictureRenderData pictures = Pictures.ofStream(inputStream,
                            PictureType.PNG).size(60, 30).create();

                    map.put("sign", pictures);
                    picTagList.add("sign");
                }

                //付款类别
                for (int i = 1; i < 6; i++) {
                    if (paymentExamineEquipment.getPaymentType().equals(i)) {
                        map.put("type" + i + "", "√");
                    } else {
                        map.put("type" + i + "", "□");
                    }
                }
                map.put("typeDescription", "（ " + paymentExamineEquipment.getPaymentTypeDescription() + " )");

                //付款依据
                for (int j = 1; j < 5; j++) {
                    if (paymentExamineEquipment.getPaymentDataType().equals(j)) {
                        map.put("dataType" + paymentExamineEquipment.getPaymentDataType() + "", "√");
                    } else {
                        map.put("dataType" + j + "", "□");
                    }
                }

                //获取初始流程
                List<SmsPaymentExamineInfrastructureProcess> processList = smsPaymentExamineInfrastructureProcessMapper.selectList(new QueryWrapper<SmsPaymentExamineInfrastructureProcess>()
                        .lambda()
                        .orderByAsc(SmsPaymentExamineInfrastructureProcess::getProcessSort));
                if (processList == null || processList.size() < 1) {
                    return new AsyncResult<>(CommonResult.failed(CommonCodeEnum.FAIL));
                }

                //获取申请流程
                List<SmsPaymentExamineInfrastructureDetail> detailList = smsPaymentExamineInfrastructureDetailMapper.selectList(new QueryWrapper<SmsPaymentExamineInfrastructureDetail>()
                        .lambda()
                        .eq(SmsPaymentExamineInfrastructureDetail::getExamineId, apply_id));
                for (SmsPaymentExamineInfrastructureProcess process : processList) {
                    List<SmsPaymentExamineInfrastructureDetail> filterDetail = detailList
                            .stream()
                            .filter(detail -> detail.getProcessId().equals(process.getId()))
                            .collect(Collectors.toList());
                    if (filterDetail.size() > 0) {
                        SmsPaymentExamineInfrastructureDetail detail = filterDetail.get(0);
                        if (detail.getDetailAllowStatus() == EXAMINE_STATUS_PASS || detail.getDetailAllowStatus() == EXAMINE_STATUS_FORCED_FINISH) {
                            map.put("allowStatus" + process.getProcessSort() + "", "同意");
                        } else if (detail.getDetailAllowStatus() == EXAMINE_STATUS_DENY || detail.getDetailAllowStatus() == EXAMINE_STATUS_FORCED_REJECT) {
                            map.put("allowStatus" + process.getProcessSort() + "", "拒绝");
                        } else {
                            map.put("allowStatus" + process.getProcessSort() + "", "");
                        }

                        map.put("allowOption" + process.getProcessSort() + "", detail.getDetailAllowOpinion());

                        //添加签名
                        if (isNullOrEmpty(detail.getDetailAllowSign())) {
                            map.put("allowSign" + process.getProcessSort() + "", "");
                        } else {
                            String[] splitStr = detail.getDetailAllowSign().split("=");
                            String fileName = splitStr[splitStr.length - 1];

                            File file = new File(filePath + fileName);
                            if (file.exists()){
                                InputStream inputStream = new FileInputStream(file);
                                PictureRenderData pictures = Pictures.ofStream(inputStream,
                                        PictureType.PNG).size(60, 30).create();

                                map.put("allowSign" + process.getProcessSort() + "", pictures);
                                picTagList.add("allowSign" + process.getProcessSort());
                            }
                        }

                        //添加印章
                        if (isNullOrEmpty(detail.getDetailAllowStamp())) {
                            map.put("allowStamp" + process.getProcessSort() + "", "");
                        } else {
                            String[] splitStr = detail.getDetailAllowStamp().split("=");
                            String fileName = splitStr[splitStr.length - 1];

                            File file = new File(filePath + fileName);
                            if (file.exists()){
                                InputStream inputStream = new FileInputStream(file);
                                PictureRenderData pictures = Pictures.ofStream(inputStream,
                                        PictureType.PNG).size(60, 60).create();

                                map.put("allowStamp" + process.getProcessSort() + "", pictures);
                                picTagList.add("allowStamp" + process.getProcessSort());
                            }
                        }

                        //审批时间
                        if (isNullOrEmpty(detail.getDetailAllowTime())) {
                            map.put("allowTime" + process.getProcessSort() + "", "");
                        } else {
                            map.put("allowTime" + process.getProcessSort() + "", TimeUtil.DateHanZiSimpleFormat(detail.getDetailAllowTime()));
                        }
                    } else {
                        map.put("allowStatus" + process.getProcessSort() + "", "");
                        map.put("allowOption" + process.getProcessSort() + "", "");
                        map.put("allowSign" + process.getProcessSort() + "", "");
                        map.put("allowStamp" + process.getProcessSort() + "", "");
                        map.put("allowTime" + process.getProcessSort() + "", "");
                    }
                }


                ClassPathResource resource = new ClassPathResource("applyTemplates/paymentExamineInfrastructureTemplate.docx");
                InputStream is = resource.getInputStream();
                FileOutputStream outputStream = new FileOutputStream(newFilePath);

                XWPFTemplate template = XWPFTemplate.compile(is);

                //配置图片标签
                Configure config = template.getConfig();
                for (String tag : picTagList
                ) {
                    config.customPolicy(tag, new PictureRenderPolicy());
                }
                template.render(map);

                template.write(outputStream);

                is.close();
                outputStream.close();
                template.close();

                //word转pdf
                File destOri = new File(newFilePath);
                FileInputStream fileInputStream = new FileInputStream(destOri);
                FileOutputStream fileOutputStream = new FileOutputStream(pdfFilePath);

                Document document = new Document();
                document.loadFromStream(fileInputStream, FileFormat.Docx);


                response.setCharacterEncoding("utf-8");
                response.setContentType("application/vnd.pdf;charset=utf-8");
                response.setHeader("Content-Disposition", "attachment;filename=" + URLEncoder.encode("付款审批表(基建)预览.pdf", "utf-8"));
                response.setHeader("file-type", "download");
                response.setHeader("file-name", URLEncoder.encode("付款审批表(基建)预览.pdf", "utf-8"));
                response.setHeader("Access-Control-Expose-Headers", "file-type,file-name");
                //刷新缓冲
                response.flushBuffer();

                //保存为PDF
//                document.saveToFile(pdfFilePath, FileFormat.PDF);
                document.saveToStream(response.getOutputStream(),FileFormat.PDF);

                fileInputStream.close();
                fileOutputStream.close();
                document.close();
                log.debug("文件生成完成!");
            } catch (Exception e) {
                e.printStackTrace();
                return new AsyncResult<>(CommonResult.failed(CommonCodeEnum.FAIL));
            }
//        }
//        try {
//            // 加载PDF文档
//            FileInputStream fileInputStream = new FileInputStream(pdfFilePath);
//            PDDocument doc = PDDocument.load(fileInputStream);
//            doc.setAllSecurityToBeRemoved(true);
//            // 创建水印
//            String watermark = "南充电影工业职业学院";
//            PDPageContentStream contentStream;
//
//            for (PDPage page : doc.getPages()) {
//                contentStream = new PDPageContentStream(doc, page, PDPageContentStream.AppendMode.APPEND, true, true);
//
//                //加载字体
//                ClassPathResource resource = new ClassPathResource("fonts/123.ttf");
//                InputStream is = resource.getInputStream();
//                PDFont font = PDType0Font.load(doc, is);
//
//
//                int startX = 0; // 起始位置 x 坐标
//                int startY = 0; // 起始位置 y 坐标
//                float angle = -45; // 角度
//                float interval = 220; // 间隔
//                float opacity = 0.3f; // 透明度
//                int colorR = 127; // 颜色 red 值
//                int colorG = 127; // 颜色 green 值
//                int colorB = 127; // 颜色 blue 值
//
//                //透明的
//                PDExtendedGraphicsState r0 = new PDExtendedGraphicsState();
//                r0.setNonStrokingAlphaConstant(opacity);
//                r0.setAlphaSourceFlag(true);
//                contentStream.setGraphicsStateParameters(r0);
//
//                //水印颜色
//                contentStream.setNonStrokingColor(colorR, colorG, colorB);
//                contentStream.beginText();
//                contentStream.setFont(font, 30f);
//
//                int x_times = (int) Math.ceil(page.getMediaBox().getWidth() / interval);
//                int y_times = (int) Math.ceil(page.getMediaBox().getHeight() / interval);
//                for (int x = startX; x <= x_times; x++) {
//                    for (int y = startY; y <= y_times; y++) {
//                        contentStream.setTextRotation(angle, (x * interval), (y * interval));
//                        contentStream.showText(watermark);
//                    }
//                }
//                contentStream.endText();
//                contentStream.restoreGraphicsState();
//                contentStream.close();
//                is.close();
//            }
//
////            response.reset();
//            response.setCharacterEncoding("utf-8");
//            response.setContentType("application/vnd.pdf;charset=utf-8");
//            response.setHeader("Content-Disposition", "attachment;filename=" + URLEncoder.encode("付款审批表(基建)预览.pdf", "utf-8"));
//            response.setHeader("file-type", "download");
//            response.setHeader("file-name", URLEncoder.encode("付款审批表(基建)预览.pdf", "utf-8"));
//            response.setHeader("Access-Control-Expose-Headers", "file-type,file-name");
//            //刷新缓冲
//            response.flushBuffer();
//
//            // 保存PDF文档
//            doc.save(response.getOutputStream());
//            fileInputStream.close();
//            doc.close();
//        } catch (Exception e) {
//            e.printStackTrace();
//            return new AsyncResult<>(CommonResult.failed(CommonCodeEnum.FAIL));
//
//        }
        return new AsyncResult<>(CommonResult.success());
    }

    private String filterResultNull(String resultStr) {
        if (resultStr == null || resultStr.equals("null")) {
            return "";
        }
        return resultStr;
    }

    @Autowired
    private SmsUserMapper smsUserMapper;

    @Override
    public ResponseResult getExamineHistoryList(String real_name, String examine_id, String contract_name, String contract_num, Integer pageNum, Integer pageSize, Integer status) {
        QueryWrapper<SmsPaymentExamineInfrastructure> queryWrapper = new QueryWrapper<>();
        if (!isNullOrEmpty(examine_id)) {
            queryWrapper.lambda().eq(SmsPaymentExamineInfrastructure::getId, examine_id);
        }
        if (!isNullOrEmpty(contract_name)) {
            queryWrapper.lambda().like(SmsPaymentExamineInfrastructure::getPaymentContractName, contract_name);
        }
        if (!isNullOrEmpty(contract_num)) {
            queryWrapper.lambda().like(SmsPaymentExamineInfrastructure::getPaymentContractNum, contract_num);
        }

        if(!isNullOrEmpty(status)){
            queryWrapper.lambda().eq(SmsPaymentExamineInfrastructure::getAllowStatus,status);
        }
        if (!isNullOrEmpty(real_name)) {
            List<String> userList = smsUserMapper.selectList(new QueryWrapper<SmsUser>()
                    .lambda()
                    .like(SmsUser::getRealName, real_name))
                    .stream()
                    .map(SmsUser::getId)
                    .collect(Collectors.toList());
            if (userList.size() > 0){
                queryWrapper.lambda().in(SmsPaymentExamineInfrastructure::getPaymentApplyUserId,userList);
            }
        }
        queryWrapper.lambda().orderByDesc(SmsPaymentExamineInfrastructure::getCreateTime);
        Page<SmsPaymentExamineInfrastructure> page = new Page<>(pageNum, pageSize);
        smsPaymentExamineInfrastructureMapper.selectPage(page, queryWrapper);

        List<SmsPaymentExamineInfrastructureResp> list = page.getRecords()
                .stream()
                .map(payment -> {
                    SmsPaymentExamineInfrastructureResp paymentExamineResp = new SmsPaymentExamineInfrastructureResp();
                    BeanUtils.copyProperties(payment, paymentExamineResp);
                    paymentExamineResp.setExamineId(payment.getId());

                    SmsUser smsUser = cacheUtil.getUserInfo(paymentExamineResp.getPaymentApplyUserId());
                    if (smsUser != null) {
                        SmsPaymentExamineInfrastructureUserResp user = new SmsPaymentExamineInfrastructureUserResp();
                        BeanUtils.copyProperties(smsUser, user);
                        paymentExamineResp.setApplyUserInfo(user);
                    }
                    return paymentExamineResp;
                })
                .collect(Collectors.toList());
        int total = (int) page.getTotal();
        return CommonResult.success(list, total);
    }

    @Autowired
    private ApiModelUtil apiModelUtil;

    @Override
    @Async
    public Future<ResponseResult> exportExamineHistoryList(SmsPaymentExamineInfrastructureHistoryReq req, HttpServletResponse response) {
        if (isNullOrEmpty(req.getIsExportProcess())) {
            return new AsyncResult<>(CommonResult.failed(CommonCodeEnum.INVALID_PARAM));
        }
        try {
            QueryWrapper<SmsPaymentExamineInfrastructure> queryWrapper = new QueryWrapper<>();
            if (!isNullOrEmpty(req.getExamineId())) {
                queryWrapper.lambda().eq(SmsPaymentExamineInfrastructure::getId, req.getExamineId());
            }
            if (!isNullOrEmpty(req.getPaymentContractName())) {
                queryWrapper.lambda().like(SmsPaymentExamineInfrastructure::getPaymentContractName, req.getPaymentContractName());
            }
            if (!isNullOrEmpty(req.getPaymentContractNum())) {
                queryWrapper.lambda().like(SmsPaymentExamineInfrastructure::getPaymentContractNum, req.getPaymentContractNum());
            }
            if (!isNullOrEmpty(req.getRealName())) {
                List<String> userList = smsUserMapper.selectList(new QueryWrapper<SmsUser>()
                        .lambda()
                        .like(SmsUser::getRealName, req.getRealName()))
                        .stream()
                        .map(SmsUser::getId)
                        .collect(Collectors.toList());
                if (userList.size() > 0){
                    queryWrapper.lambda().in(SmsPaymentExamineInfrastructure::getPaymentApplyUserId,userList);
                }
            }
            queryWrapper.lambda().orderByDesc(SmsPaymentExamineInfrastructure::getCreateTime);
            List<SmsPaymentExamineInfrastructure> list = smsPaymentExamineInfrastructureMapper.selectList(queryWrapper);
            //表头数据
            String[] header = req.getLimitColumn().toArray(new String[0]);
            double sheetNum;
            //声明一个工作簿
            HSSFWorkbook workbook = new HSSFWorkbook();
            if (list != null && list.size() > 0) {
                sheetNum = Math.ceil((double) list.size() / PER_SHEET_NUM);
                for (int k = 0; k < sheetNum; k++) {
                    //生成一个表格，设置表格名称为"资源导出表"
                    HSSFSheet sheet = workbook.createSheet("付款审批表(基建)记录导出表" + (k + 1));

                    //设置表格列宽度为10个字节
                    sheet.setDefaultColumnWidth(12);
                    //创建标题的显示样式
                    HSSFCellStyle headerStyle = workbook.createCellStyle();
                    headerStyle.setFillForegroundColor(IndexedColors.YELLOW.index);
                    headerStyle.setFillPattern(FillPatternType.SOLID_FOREGROUND);

                    HSSFFont f = workbook.createFont();
                    f.setFontHeightInPoints((short) 10);//字号
                    f.setBold(true);//加粗
                    headerStyle.setFont(f);
                    //创建第一行表头
                    HSSFRow headrow = sheet.createRow(0);

                    //遍历添加表头(下面模拟遍历学生，也是同样的操作过程)
                    for (int i = 0; i < header.length + 1; i++) {
                        //创建一个单元格
                        HSSFCell cell = headrow.createCell(i);

                        if (i == 0) {
                            //创建一个内容对象
                            HSSFRichTextString text = new HSSFRichTextString("序号");
                            //将内容对象的文字内容写入到单元格中
                            cell.setCellValue(text);
                            cell.setCellStyle(headerStyle);
                            continue;
                        }
                        //创建一个内容对象
                        String header1 = apiModelUtil.getFieldValueByFieldName(SmsPaymentExamineInfrastructure.class, header[i - 1]);
                        HSSFRichTextString text = new HSSFRichTextString(header1);

                        //将内容对象的文字内容写入到单元格中
                        cell.setCellValue(text);
                        cell.setCellStyle(headerStyle);
                    }

                    //判断是否需要添加流程表头
                    if (req.getIsExportProcess() == EXPORT_PROCESS_TRUE) {
                        List<SmsPaymentExamineInfrastructureProcess> processList =
                                smsPaymentExamineInfrastructureProcessMapper.selectList(new QueryWrapper<>());
                        if (processList != null && processList.size() > 0) {
                            Integer origin_num = header.length + 1;
                            for (SmsPaymentExamineInfrastructureProcess process : processList) {
                                String process_name = process.getProcessName();
                                addProcessTableHead(headrow, headerStyle, origin_num, process_name);
                                origin_num += 4;
                            }
                        }
                    }

                    int range = PER_SHEET_NUM;
                    if (k + 1 == sheetNum) {
                        range = list.size() - (PER_SHEET_NUM) * k;
                    }
                    for (int i = 0; i < range; i++) {
                        //创建一行
                        HSSFRow row1 = sheet.createRow(i + 1);
                        SmsPaymentExamineInfrastructure paymentExamine = list.get((PER_SHEET_NUM) * k + i);
                        Map map = JSONObject.parseObject(JSON.toJSONString(paymentExamine), Map.class);
                        row1.createCell(0).setCellValue(new HSSFRichTextString(i + 1 + ""));
                        for (int j = 0; j < header.length; j++) {
                            String rowContent = "";
                            if (map.get(header[j]) instanceof Long) {
                                rowContent = TimeUtil.DateformatTimestamp((long) map.get(header[j]));
                            } {
                                if (header[j].equals("paymentApplyUserId")) {
                                    SmsUser smsUser = cacheUtil.getUserInfo(paymentExamine.getPaymentApplyUserId());
                                    if (smsUser != null) {
                                        rowContent = smsUser.getRealName();
                                    } else {
                                        rowContent = "";
                                    }
                                } else if (header[j].equals("paymentDateFile")) {
                                    rowContent = "";
                                } else {
                                    rowContent = String.valueOf(map.get(header[j]));
                                }
                            }
                            row1.createCell(j + 1).setCellValue(new HSSFRichTextString(rowContent));
                        }

                        if (req.getIsExportProcess() == EXPORT_PROCESS_TRUE) {
                            List<SmsPaymentExamineInfrastructureProcess> processList =
                                    smsPaymentExamineInfrastructureProcessMapper.selectList(new QueryWrapper<>());
                            if (processList != null && processList.size() > 0) {
                                Integer origin_num = header.length + 1;
                                for (SmsPaymentExamineInfrastructureProcess process : processList) {
                                    SmsPaymentExamineInfrastructureDetail detail =
                                            smsPaymentExamineInfrastructureDetailMapper.selectOne(new QueryWrapper<SmsPaymentExamineInfrastructureDetail>()
                                                    .lambda()
                                                    .eq(SmsPaymentExamineInfrastructureDetail::getExamineId, paymentExamine.getId())
                                                    .eq(SmsPaymentExamineInfrastructureDetail::getProcessId, process.getId()));
                                    if (detail == null || detail.getId() == null) {
                                        origin_num += 4;
                                    } else {
                                        //审批人
                                        SmsUser user = cacheUtil.getUserInfo(detail.getDetailAllowUserId());
                                        if (user == null) {
                                            row1.createCell(origin_num++).setCellValue(new HSSFRichTextString(""));
                                        } else {
                                            row1.createCell(origin_num++).setCellValue(new HSSFRichTextString(user.getRealName()));
                                        }

                                        //审批时间
                                        Date allow_time = detail.getDetailAllowTime();
                                        if (allow_time == null) {
                                            row1.createCell(origin_num++).setCellValue(new HSSFRichTextString(""));
                                        } else {
                                            row1.createCell(origin_num++).setCellValue(new HSSFRichTextString(TimeUtil.DateHanZiSimpleFormat(allow_time)));
                                        }

                                        //审批状态
                                        Integer allow_status = detail.getDetailAllowStatus();
                                        if (allow_status == EXAMINE_STATUS_PASS || allow_status == EXAMINE_STATUS_FORCED_FINISH) {
                                            row1.createCell(origin_num++).setCellValue(new HSSFRichTextString("同意"));
                                        } else if (allow_status == EXAMINE_STATUS_DENY || allow_status == EXAMINE_STATUS_FORCED_REJECT) {
                                            row1.createCell(origin_num++).setCellValue(new HSSFRichTextString("拒绝"));
                                        } else {
                                            row1.createCell(origin_num++).setCellValue(new HSSFRichTextString(""));
                                        }

                                        //审批意见
                                        String allow_option = detail.getDetailAllowOpinion();
                                        if (isNullOrEmpty(allow_option)) {
                                            row1.createCell(origin_num++).setCellValue(new HSSFRichTextString(""));
                                        } else {
                                            row1.createCell(origin_num++).setCellValue(new HSSFRichTextString(allow_option));
                                        }
                                    }
                                }
                            }
                        }
                    }
                }
            }

//            response.reset();
            response.setContentType("application/vnd.ms-excel;charset=utf-8");
            response.setHeader("Content-Disposition", "attachment;filename=" + URLEncoder.encode("付款审批表(基建)记录导出表.xlsx", "utf-8"));
            response.setCharacterEncoding("utf-8");
            response.setHeader("file-type", "download");
            response.setHeader("file-name", URLEncoder.encode("付款审批表(基建)记录导出表.xlsx", "utf-8"));
            response.setHeader("Access-Control-Expose-Headers", "file-type,file-name");
//            //刷新缓冲
            response.flushBuffer();
            //workbook将Excel写入到response的输出流中，供页面下载
            OutputStream os = response.getOutputStream();
            workbook.write(os);

            workbook.close();
            os.close();
        } catch (Exception e) {
            e.printStackTrace();
            return new AsyncResult<>(CommonResult.failed(CommonCodeEnum.FAIL));
        }
        return null;
    }



    private void addProcessTableHead(HSSFRow headRow, HSSFCellStyle headerStyle, Integer origin_cell_num, String originHeadContent) {
        Integer cell_num = origin_cell_num;

        setTableHead(headRow, headerStyle, cell_num++, originHeadContent + "审批人");
        setTableHead(headRow, headerStyle, cell_num++, originHeadContent + "审批时间");
        setTableHead(headRow, headerStyle, cell_num++, originHeadContent + "审批状态");
        setTableHead(headRow, headerStyle, cell_num, originHeadContent + "审批意见");

    }

    private void setTableHead(HSSFRow headRow, HSSFCellStyle headerStyle, Integer cell_num, String headContent) {
        HSSFCell cell = headRow.createCell(cell_num);
        //创建一个内容对象
        HSSFRichTextString text = new HSSFRichTextString(headContent);

        //将内容对象的文字内容写入到单元格中
        cell.setCellValue(text);
        cell.setCellStyle(headerStyle);
    }
    @Override
    @Transactional
    public ResponseResult forcedFinishPayment(String applyId, String userId) {
        //校验数据
        if (isNullOrEmpty(applyId)) {
            return CommonResult.failed(CommonCodeEnum.INVALID_PARAM);
        }
        SmsPaymentExamineInfrastructure smsPaymentExamineInfrastructure = smsPaymentExamineInfrastructureMapper.selectById(applyId);
        if(isNullOrEmpty(smsPaymentExamineInfrastructure)){
            return CommonResult.failed(CommonCodeEnum.PAYMENT_NOT_EXIST);
        }
        if(smsPaymentExamineInfrastructure.getAllowStatus() != EXAMINE_STATUS_WAIT_ALLOW){
            return CommonResult.failed(CommonCodeEnum.PAYMENT_NOT_FORCED);
        }
        //修改审批表状态为通过
        smsPaymentExamineInfrastructure.setAllowStatus(EXAMINE_STATUS_PASS);
        smsPaymentExamineInfrastructure.setEndTime(new Date());
        smsPaymentExamineInfrastructureMapper.updateById(smsPaymentExamineInfrastructure);

        //修改节点为强制归档
        SmsPaymentExamineInfrastructureDetail smsPaymentExamineInfrastructureDetail = new SmsPaymentExamineInfrastructureDetail();
        smsPaymentExamineInfrastructureDetail.setDetailAllowStatus(EXAMINE_STATUS_FORCED_FINISH);
        smsPaymentExamineInfrastructureDetail.setDetailAllowUserId(userId);
        smsPaymentExamineInfrastructureDetail.setDetailAllowTime(new Date());
        smsPaymentExamineInfrastructureDetailMapper.update(smsPaymentExamineInfrastructureDetail,new LambdaQueryWrapper<SmsPaymentExamineInfrastructureDetail>()
                .eq(SmsPaymentExamineInfrastructureDetail::getExamineId,applyId)
                .eq(SmsPaymentExamineInfrastructureDetail::getDetailAllowStatus,EXAMINE_STATUS_WAIT_ALLOW));

        //消息通知
        newTipsUtil.cancelFinishTips(applyId);

        return CommonResult.success();
    }

    @Override
    @Transactional
    public ResponseResult forcedTorsionPayment(SmsPaymentExamineEquipmentDetailTorsionReq torsionVO) {
        if(isNullOrEmpty(torsionVO.getDetailId(),torsionVO.getApplyId(),torsionVO.getProcessObjectType(),torsionVO.getProcessObjectId())){
            return CommonResult.failed(CommonCodeEnum.INVALID_PARAM);
        }
        SmsPaymentExamineInfrastructure smsPaymentExamineInfrastructure = smsPaymentExamineInfrastructureMapper.selectById(torsionVO.getApplyId());
        if(isNullOrEmpty(smsPaymentExamineInfrastructure)){
            return CommonResult.failed(CommonCodeEnum.PAYMENT_NOT_EXIST);
        }
        SmsPaymentExamineInfrastructureDetail detail = smsPaymentExamineInfrastructureDetailMapper.selectById(torsionVO.getDetailId());
        if(isNullOrEmpty(detail)){
            return CommonResult.failed(CommonCodeEnum.PAYMENT_DETAIL_NOT_FORCED);
        }
        if(detail.getDetailAllowStatus() != EXAMINE_STATUS_WAIT_ALLOW){
            return CommonResult.failed(CommonCodeEnum.PAYMENT_NOT_TORSION);
        }
        detail.setProcessObjectType(torsionVO.getProcessObjectType());
        detail.setProcessObjectId(torsionVO.getProcessObjectId());
        smsPaymentExamineInfrastructureDetailMapper.updateById(detail);
        //消息通知
        //判断第一节点直接发消息,其他要前节点审批后才发该节点通知
        boolean flag = true;
        if(!detail.getDetailSort().equals(1)){
            SmsPaymentExamineInfrastructureDetail beforeDetail = smsPaymentExamineInfrastructureDetailMapper.selectOne(new LambdaQueryWrapper<SmsPaymentExamineInfrastructureDetail>()
                    .eq(SmsPaymentExamineInfrastructureDetail::getExamineId, torsionVO.getApplyId())
                    .eq(SmsPaymentExamineInfrastructureDetail::getDetailSort, detail.getDetailSort() - 1));
            if(beforeDetail.getDetailAllowStatus() != EXAMINE_STATUS_PASS){
                flag = false;
            }
        }

        if(flag) {
            RangeTypeEnum rangeTypeEnum;
            if (detail.getProcessObjectType() == AGREEMENT_OBJECT_TYPE_PERSON) {
                rangeTypeEnum = RangeTypeEnum.RANGE_TYPE_ENUM_PERSON;
            } else {
                rangeTypeEnum = RangeTypeEnum.RANGE_TYPE_ENUM_ROLE;
            }
            List<String> rangeList = new ArrayList<>();
            rangeList.add(detail.getProcessObjectId());
            newTipsUtil.allowContinueTips(torsionVO.getApplyId(),
                    null,
                    rangeTypeEnum,
                    rangeList,
                    detail.getId());
        }
        return CommonResult.success();
    }

    @Override
    @Transactional
    public ResponseResult replaceApplyTorsionPayment(String userId, SmsPaymentExamineInfrastructureAllowReq smsPaymentExamineAllowReq) {
        if (isNullOrEmpty(smsPaymentExamineAllowReq.getExamine_id()) || isNullOrEmpty(smsPaymentExamineAllowReq.getDetail_id())
                || isNullOrEmpty(smsPaymentExamineAllowReq.getDetailAllowStatus())) {
            return CommonResult.failed(CommonCodeEnum.INVALID_PARAM);
        }

        if (smsPaymentExamineAllowReq.getDetailAllowStatus() != EXAMINE_STATUS_PASS
                && smsPaymentExamineAllowReq.getDetailAllowStatus() != EXAMINE_STATUS_DENY) {
            return CommonResult.failed(CommonCodeEnum.INVALID_PARAM);
        }

        SmsPaymentExamineInfrastructureDetail paymentExamineDetail =
                smsPaymentExamineInfrastructureDetailMapper.selectOne(new QueryWrapper<SmsPaymentExamineInfrastructureDetail>()
                        .lambda()
                        .eq(SmsPaymentExamineInfrastructureDetail::getExamineId, smsPaymentExamineAllowReq.getExamine_id())
                        .eq(SmsPaymentExamineInfrastructureDetail::getId, smsPaymentExamineAllowReq.getDetail_id())
                        .eq(SmsPaymentExamineInfrastructureDetail::getDetailAllowStatus, EXAMINE_STATUS_WAIT_ALLOW));
        if (paymentExamineDetail == null || isNullOrEmpty(paymentExamineDetail.getId())) {
            return CommonResult.failed(CommonCodeEnum.PAYMENT_ALLOW_FAIL);
        }


        if (!paymentExamineDetail.getDetailSort().equals(1)) {
            SmsPaymentExamineInfrastructureDetail preDetail =
                    smsPaymentExamineInfrastructureDetailMapper.selectOne(new QueryWrapper<SmsPaymentExamineInfrastructureDetail>()
                            .lambda()
                            .eq(SmsPaymentExamineInfrastructureDetail::getExamineId, smsPaymentExamineAllowReq.getExamine_id())
                            .eq(SmsPaymentExamineInfrastructureDetail::getDetailSort, paymentExamineDetail.getDetailSort() - 1));
            if (preDetail != null && !isNullOrEmpty(preDetail.getId())) {
                if (preDetail.getDetailAllowStatus() != EXAMINE_STATUS_PASS) {
                    return CommonResult.failed(CommonCodeEnum.PAYMENT_ALLOW_FAIL);
                }
            }
        }

        //判断是否监理部门
        if (paymentExamineDetail.getProcessName().equals("监理部门")) {
            if (isNullOrEmpty(smsPaymentExamineAllowReq.getJianliDepartmentName())) {
                return CommonResult.failed(CommonCodeEnum.PAYMENT_PROCESS_JIANLI_NOT_FILL);
            }

            SmsPaymentExamineInfrastructure updateExamine = new SmsPaymentExamineInfrastructure();
            updateExamine.setId(smsPaymentExamineAllowReq.getExamine_id());
            updateExamine.setJianliDepartmentName(smsPaymentExamineAllowReq.getJianliDepartmentName());

            smsPaymentExamineInfrastructureMapper.updateById(updateExamine);
        }

        //判断是否审计部门
        if (paymentExamineDetail.getProcessName().equals("审计部门")) {
            if (isNullOrEmpty(smsPaymentExamineAllowReq.getShenjiDepartmentName())) {
                return CommonResult.failed(CommonCodeEnum.PAYMENT_PROCESS_SHENJI_NOT_FILL);
            }

            SmsPaymentExamineInfrastructure updateExamine = new SmsPaymentExamineInfrastructure();
            updateExamine.setId(smsPaymentExamineAllowReq.getExamine_id());
            updateExamine.setShenjiDepartmentName(smsPaymentExamineAllowReq.getShenjiDepartmentName());

            smsPaymentExamineInfrastructureMapper.updateById(updateExamine);
        }


        //判断是否财务部 财务部填写审批金额
        if (smsPaymentExamineAllowReq.getDetailAllowStatus() == EXAMINE_STATUS_PASS && paymentExamineDetail.getProcessName().equals("财务部")) {
            if (isNullOrEmpty(smsPaymentExamineAllowReq.getPaymentExamineMoney())) {
                return CommonResult.failed(CommonCodeEnum.PAYMENT_PROCESS_FINANCE_NOT_FILL);
            }

            SmsPaymentExamineInfrastructure updateExamine = new SmsPaymentExamineInfrastructure();
            updateExamine.setId(smsPaymentExamineAllowReq.getExamine_id());
            updateExamine.setPaymentExamineMoney(smsPaymentExamineAllowReq.getPaymentExamineMoney());

            smsPaymentExamineInfrastructureMapper.updateById(updateExamine);
        }

        SmsPaymentExamineInfrastructureDetail allowDetail = new SmsPaymentExamineInfrastructureDetail();
        allowDetail.setId(smsPaymentExamineAllowReq.getDetail_id());
        allowDetail.setDetailAllowStatus(smsPaymentExamineAllowReq.getDetailAllowStatus());
        if (!isNullOrEmpty(smsPaymentExamineAllowReq.getDetailAllowOpinion())) {
            allowDetail.setDetailAllowOpinion(smsPaymentExamineAllowReq.getDetailAllowOpinion());
        }
        Date nowDate = new Date();
        allowDetail.setDetailAllowTime(nowDate);
        allowDetail.setDetailAllowUserId(userId);
        allowDetail.setDetailAllowSign(smsPaymentExamineAllowReq.getDetailAllowSign());
        allowDetail.setDetailAllowStamp(smsPaymentExamineAllowReq.getDetailAllowStamp());

        smsPaymentExamineInfrastructureDetailMapper.updateById(allowDetail);

        boolean is_done = false;

        //判断是否最后一个节点 是否驳回
        Integer detailCount = smsPaymentExamineInfrastructureDetailMapper.selectCount(new QueryWrapper<SmsPaymentExamineInfrastructureDetail>()
                .lambda()
                .eq(SmsPaymentExamineInfrastructureDetail::getExamineId, smsPaymentExamineAllowReq.getExamine_id()));
        if (detailCount.equals(paymentExamineDetail.getDetailSort()) || smsPaymentExamineAllowReq.getDetailAllowStatus() == EXAMINE_STATUS_DENY) {
            is_done = true;

            SmsPaymentExamineInfrastructure updatePaymentExamine = new SmsPaymentExamineInfrastructure();
            updatePaymentExamine.setId(smsPaymentExamineAllowReq.getExamine_id());
            updatePaymentExamine.setEndTime(nowDate);
            updatePaymentExamine.setAllowStatus(smsPaymentExamineAllowReq.getDetailAllowStatus());
            smsPaymentExamineInfrastructureMapper.updateById(updatePaymentExamine);
        }

        //节点驳回 重置其余节点状态
        if (smsPaymentExamineAllowReq.getDetailAllowStatus() == EXAMINE_STATUS_DENY) {
            SmsPaymentExamineInfrastructureDetail updateDenyDetail =
                    new SmsPaymentExamineInfrastructureDetail();
            updateDenyDetail.setDetailAllowStatus(EXAMINE_STATUS_DENY_FINISH);
            smsPaymentExamineInfrastructureDetailMapper.update(updateDenyDetail, new QueryWrapper<SmsPaymentExamineInfrastructureDetail>()
                    .lambda()
                    .eq(SmsPaymentExamineInfrastructureDetail::getExamineId, smsPaymentExamineAllowReq.getExamine_id())
                    .eq(SmsPaymentExamineInfrastructureDetail::getDetailAllowStatus, EXAMINE_STATUS_WAIT_ALLOW));
        }

        //消息通知
        if (is_done) {
            boolean result_status = false;
            if (smsPaymentExamineAllowReq.getDetailAllowStatus() == EXAMINE_STATUS_PASS) {
                result_status = true;
            }
            newTipsUtil.allowFinishTips(smsPaymentExamineAllowReq.getExamine_id(), userId, result_status);
        } else {
            SmsPaymentExamineInfrastructureDetail nextDetail =
                    smsPaymentExamineInfrastructureDetailMapper.selectOne(new QueryWrapper<SmsPaymentExamineInfrastructureDetail>()
                            .lambda()
                            .eq(SmsPaymentExamineInfrastructureDetail::getExamineId, smsPaymentExamineAllowReq.getExamine_id())
                            .eq(SmsPaymentExamineInfrastructureDetail::getDetailSort, paymentExamineDetail.getDetailSort() + 1));
            RangeTypeEnum rangeTypeEnum = RangeTypeEnum.RANGE_TYPE_ENUM_PERSON;
            if (nextDetail.getProcessObjectType() == EXAMINE_OBJECT_TYPE_ROLE) {
                rangeTypeEnum = RangeTypeEnum.RANGE_TYPE_ENUM_ROLE;
            }
            List<String> rangeIDList = new ArrayList<>();
            rangeIDList.add(nextDetail.getProcessObjectId());
            newTipsUtil.allowContinueTips(smsPaymentExamineAllowReq.getExamine_id(),
                    null,
                    rangeTypeEnum,
                    rangeIDList,
                    nextDetail.getId());
        }
        return CommonResult.success();
    }

    @Override
    @Transactional
    public ResponseResult forcedRejectPayment(SmsPaymentExamineEquipmentForcedReq forcedReq, String userId) {
        if(isNullOrEmpty(forcedReq.getApplyId(),forcedReq.getDetailAllowOption())){
            return CommonResult.failed(CommonCodeEnum.INVALID_PARAM);
        }
        //校验
        SmsPaymentExamineInfrastructure paymentExamineInfrastructure = smsPaymentExamineInfrastructureMapper.selectById(forcedReq.getApplyId());
        if(isNullOrEmpty(paymentExamineInfrastructure)){
            return CommonResult.failed(CommonCodeEnum.PAYMENT_NOT_EXIST);
        }
        //总状态为代审批才能强制驳回
        Integer allowStatus = paymentExamineInfrastructure.getAllowStatus();
        if(allowStatus != EXAMINE_STATUS_WAIT_ALLOW){
            return CommonResult.failed(CommonCodeEnum.PAYMENT_NOT_FORCED_REJECT);
        }
        //修改审批表状态为驳回
        paymentExamineInfrastructure.setAllowStatus(EXAMINE_STATUS_DENY);
        paymentExamineInfrastructure.setEndTime(new Date());
        smsPaymentExamineInfrastructureMapper.updateById(paymentExamineInfrastructure);
        //修改节点状态为强制驳回
        SmsPaymentExamineInfrastructureDetail paymentExamineInfrastructureDetail = new SmsPaymentExamineInfrastructureDetail();
        paymentExamineInfrastructureDetail.setDetailAllowUserId(userId);
        paymentExamineInfrastructureDetail.setDetailAllowStatus(EXAMINE_STATUS_FORCED_REJECT);
        paymentExamineInfrastructureDetail.setDetailAllowTime(new Date());
        paymentExamineInfrastructureDetail.setDetailAllowOpinion(forcedReq.getDetailAllowOption());
        smsPaymentExamineInfrastructureDetailMapper.update(paymentExamineInfrastructureDetail,new LambdaQueryWrapper<SmsPaymentExamineInfrastructureDetail>()
        .eq(SmsPaymentExamineInfrastructureDetail::getExamineId,forcedReq.getApplyId())
        .eq(SmsPaymentExamineInfrastructureDetail::getDetailAllowStatus,EXAMINE_STATUS_WAIT_ALLOW));
        //消息提醒
        newTipsUtil.cancelFinishTips(forcedReq.getApplyId());
        return CommonResult.success();
    }

}
